<?php
class CourseDetail extends AppModel {
	var $useTable = 'courses_detail';
	var $primaryKey = 'id';
	var $name = 'CourseDetail';
	var $order = 'opening_date desc';
	const CALENDAR_COURSE_LIMIT = 5;
	
	var $belongsTo = array(
		'Area' => array(
			'className' => 'Area',
			'foreignKey' => 'area',
		),
		'Course' => array(
			'className' => 'Course',
			'foreignKey' => 'course_id',
		),
	);

	var $hasAndBelongsToMany = array(
		'PaymentMethod' => array(
			'className' => 'PaymentMethod',
			'joinTable' => 'relation_payment',
			'foreignKey' => 'detail_id',
			'associationForeignKey' => 'payment_id',
			'unique' => true
		)
	);

	var $validate = array(
		'attend_total' => array(
			'numeric' => array(
				'rule' => 'numeric',
				'required' => true,
				'message' => Messages::course_attend_total_is_required,
			),
			'minvalue' => array(
				'rule' => array('comparison', '>=', 1),
				'message' => Messages::course_attend_total_is_required
			)
			
		),
		'opening_date' => array(
			'datetime_rule' => array(
				'required' => false,
				'allowEmpty' => true,
				'rule' => '/^\d{4}\-\d{1,2}\-\d{1,2}\s\d{1,2}:\d{1,2}\:\d{1,2}$/i',
				'message' => Messages::please_input_correct_date_time_format,
			)
		),
		'closing_date' => array(
			'datetime_rule' => array(
				'required' => false,
				'allowEmpty' => true,
				'rule' => '/^\d{4}\-\d{1,2}\-\d{1,2}\s\d{1,2}:\d{1,2}\:\d{1,2}$/i',
				'message' => Messages::please_input_correct_date_time_format,
			)
		),
		'address01' => array(
			'rule' => 'notEmpty',
			'message' => Messages::address01_can_not_be_left_blank
		),
		'address02' => array(
			'rule' => 'notEmpty',
			'message' => Messages::address01_can_not_be_left_blank
		),
		'price' => array(
			'numeric' => array(
				'rule' => 'numeric',
				'required' => true,
				'message' => Messages::price_must_be_numeric
			),
			'minvalue' => array(
				'rule' => array('comparison', '>=', 1),
				'message' => Messages::price_must_be_large_than_0
			)
			
		)
	);

	/**
	 * Get option for paginate in controller
	 * @return array
	 */
	function getPaginateOption() {
		$options = array();
		$options['joins'] = array(
			array(
				'table' => '(SELECT count(ec.user_id) AS entered_counting, ec.detail_id FROM entered_courses ec WHERE ec.del_flg = 0 GROUP BY ec.detail_id)',
				'alias' => 'CourseCounting',
				'type' => 'LEFT',
				'conditions' => array(
					'CourseDetail.id = CourseCounting.detail_id'
				)
			)
		);
		$options['fields'] = array(
			'Course.*',
			'CourseDetail.*',
			'Area.name',
			'CourseCounting.entered_counting',
		);
		$options['conditions'] = array(
			'CourseDetail.del_flg' => 0,
		);
		return $options;
	}
	/**
	 * Get course detail by course detail id
	 *
	 * @param $id
	 * @param $moreOptions - more options
	 * @return array
	 */
	function getCourseDetail($id, $moreOptions = array()) {
		$options = $this->getPaginateOption();
		$options = array_merge($options, $moreOptions);

		$options['conditions']['CourseDetail.id'] = $id;
		return $this->find('first', $options);
	}

	/**
	 * Get the list schedules by the course id that it belong to
	 *
	 * @param $id
	 * @return array
	 */
	function listDetailByCourseId($id) {
		$options = array();
		$options['fields'] = array(
			$this->alias . '.*',
			$this->Area->alias . '.name',
		);
		$options['conditions'] = array(
			$this->alias . '.course_id' => $id,
			$this->alias . '.del_flg' => 0,
		);
		$options['recursive'] = 0;
		return $this->find('all', $options);
	}

	/**
	 * Update del_flg of course detail table by its id
	 *
	 * @param $detailId
	 * @param $userId
	 * @param $value
	 */
	function updateDeleteFlgByUserId($detailId, $userId, $value) {
		if ($value != 0) {
			$value = 1;
		}

		$conditions = array(
			$this->alias . '.id' => $detailId,
			$this->alias .'.course_id IN (SELECT c.id FROM courses c WHERE c.user_id = ' . intval($userId) . ')',
		);
		$this->updateAll(array('del_flg' => $value), $conditions);
	}

	/**
	 * Check if user is owner of course detail
	 *
	 * @param $detailId
	 * @param $userId
	 * @return bool
	 */
	function isOwner($detailId, $userId) {
		$options = array();
		$options['conditions'] = array(
			$this->alias . '.id' => $detailId,
			$this->alias .'.course_id IN (SELECT c.id FROM courses c WHERE c.user_id = ' . intval($userId) . ')',
		);
		//$options['recursive'] = -1;
		if ($this->find('count', $options)) {
			return true;
		} else {
			return false;
		}
	}

	/**
	 * Check if course detail is full or not
	 *
	 * @param $detailId
	 * @return bool
	 */
	function isFull($detailId) {
		$options = array();
		App::import('model', 'EnteredCourse');
		$entered = new EnteredCourse();
		$options['conditions'] = array(
			$entered->alias . '.del_flg' => 0,
			$entered->alias . '.detail_id' => $detailId,
		);
		$options['recursive'] = -1;
		$joined = $entered->find('count', $options);

		$detail = $this->read(array('attend_total'), $detailId);
		if ($detail['CourseDetail']['attend_total'] <= $joined) {
			return true;
		} else {
			return false;
		}
	}

	/**
	 * Get course detail for enter course, leave course
	 * @param $detailId
	 * @param $courseId
	 * @return mixed Result of find function
	 */
	function getForEnter($detailId, $courseId) {
		$options = array();
		$options['conditions'] = array(
			$this->alias . '.del_flg' => 0,
			$this->alias . '.id' => $detailId,
			$this->alias . '.course_id' => $courseId,
		);
		$options['fields'] = array(
			'CourseDetail.*',
			'Area.name',
		);
		return $this->find('first', $options);
	}

	/**
	 * Get course detail by id
	 * @param $detailId
	 * @return mixed
	 */
	function getById ($detailId) {
		$options = array(
			'fields' => array(
				'CourseDetail.*',
				'Course.*'
			),
			'conditions' => array(
				'CourseDetail.id' => $detailId,
			),
			'recursive' => 0,
		);

		return $this->find('first', $options);
	}

	/**
	 * Get list schedules of course, include information about opening date, closing date, price..., and users have joined
	 * to this schedule
	 *
	 * @param $courseId
	 * @return array
	 */
	function getForNotification($courseId) {
		$options = array(
			'fields' => array(
				$this->alias . '.*',
				'EnteredCourse.user_id',
			),
			'conditions' => array(
				$this->alias . '.course_id' => $courseId,
				$this->alias . '.del_flg' => 0,
			),
			'recursive' => -1,
			'joins' => array(
				array(
					'table' => 'entered_courses',
					'alias' => 'EnteredCourse',
					'type' => 'INNER',
					'conditions' => array(
						$this->alias . '.id = EnteredCourse.detail_id AND EnteredCourse.del_flg = 0'
					)
				),
				array(
					'table' => 'transactions',
					'alias' => 'Transaction',
					'type' => 'INNER',
					'conditions' => array(
						'Transaction.id = EnteredCourse.transaction_id AND Transaction.del_flg = 0 AND Transaction.status = 1'
					)
				),
			)
		);

		return $this->find('all', $options);
	}

	/**
	 * Check if user could leave a course detail
	 *
	 * @param $detail
	 * @return bool
	 */
	function canLeave($detail) {
		if (isset($detail['CourseDetail']['id'])) {
			if (strtotime($detail['CourseDetail']['opening_date']) > Configure::read('Course.limit_leave_time')) {
				return true;
			} else {
				return false;
			}
		} else {
			trigger_error('There no data for check leaving');
		}
	}
	/**
	 * validate data and validate opening_date and closing_date
	 * @return boolean
	 */
	function validateCourseDetail() {
		if($this->validates()){
			$openDate = strtotime($this->data[$this->alias]['opening_date']);
			$closeDate = strtotime($this->data[$this->alias]['closing_date']);
			if(!$openDate || $openDate < strtotime(date('Y-m-d H:i:s'))){// because don't check valid day of month at front page ==> check it @^@
				$this->validationErrors['opening_date'] = Messages::invalid_opening_date;
				return false;
			}
			if(!$closeDate || $closeDate < strtotime(date('Y-m-d H:i:s'))){
				$this->validationErrors['closing_date'] = Messages::invalid_closing_date;
				return false;
			}
			if($closeDate <= $openDate ){
				$this->validationErrors['closing_date'] = Messages::invalid_closing_date_can_not_less_than_the_opening_date;
				return false;
			}
			return true;
		}else{
			return false;
		}
	}
	
	function getCourseDetailInDuration($start, $end , $limit) {
		$options['joins'] = array(
			array(
				'table' => 'courses',
				'alias' => 'Course',
				'type' => 'inner', 
				'conditions' => array(
					$this->alias . '.course_id = Course.id',
					'Course.del_flg = 0'
				),
			)
		);
		$options['recursive'] = -1;
		$options['conditions'] = array(
			$this->alias . ".opening_date between '" . $start ."' and '" . $end . "'",
			$this->alias . ".del_flg" => 0
		);
		if(isset($limit)) {
			$options['limit'] = $limit;
		}
		$options['order'] = array('opening_date' => 'ASC');
		$options['fields'] = array(
			'Course.title', 'Course.id', $this->alias . '.opening_date', $this->alias . '.closing_date'
		);
		
		return $this->find('all', $options);
	}
	
	function countCourseDetailInDuration($start, $end) {
		$options['conditions'] = array(
			$this->alias . ".opening_date between '" . $start ."' and '" . $end . "'",
			$this->alias . ".del_flg" => 0
		);
		$options['recursive'] = -1;
		$options['order'] = array('opening_date' => 'ASC');
		return $this->find('count', $options);
	}
}